import 'dart:io';

import 'package:file_picker/file_picker.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart';

import '../platform_service.dart';
import 'platform_service_platform_interface.dart';
import 'util/water_mark_util.dart';

/// An implementation of [PlatformServicePlatform] that uses method channels.
class MethodChannelPlatformService extends PlatformServicePlatform {
  /// The method channel used to interact with the native platform.
  @visibleForTesting
  final methodChannel = const MethodChannel('platform_service');

  @override
  Future<String?> getPlatformVersion() async {
    final version =
        await methodChannel.invokeMethod<String>('getPlatformVersion');
    return version;
  }

  @override
  Future<NDFilePickerResult> pickFile() async {
    try {
      FilePickerResult? result =
          await FilePicker.platform.pickFiles(allowMultiple: true);
      return Future.value(NDFilePickerResult(result?.files ?? []));
    } catch (err) {
      debugPrint('err：${err.toString()}');
      return Future.value(NDFilePickerResult([]));
    }
  }

  @override
  Future<List<NDFileInfo>> pickImages(
      {int maxCount = 8,
      bool enableCamera = false,
      bool isWaterMark = false,
      bool isWaterMarkTiled = false,
      List<ImageWaterMarkSettingModel>? waterMarkSettings}) async {
    try {
      List<NDFileInfo> selectImages = [];
      var arg = {'maxCount': maxCount, 'enableCamera': enableCamera};
      var result = await methodChannel.invokeMethod<List>('pickImages', arg);
      if (result != null) {
        if (isWaterMark) {
          int index = 0;
          for (var localPath
              in (await NDWaterMarkerUtil.watermark<List<String>>(
                  result, waterMarkSettings ?? [], isWaterMarkTiled))) {
            if (localPath.isNotEmpty) {
              var size = result[index]['size'] as int?;
              size = await _fileSize(size, localPath);
              selectImages.add(NDFileInfo(
                name: result[index]['name'],
                size: size,
                path: localPath,
                mimeType: result[index]['mimeType'],
              ));
            }
            index++;
          }
        } else {
          for (var m in result) {
            var size = m['size'] as int?;
            var localPath = m['localPath'] as String;
            size = await _fileSize(size, localPath);
            String name = m['name'] ?? localPath.split('/').last ?? '-';
            selectImages.add(NDFileInfo(
              name: name,
              size: size,
              path: localPath,
              mimeType: m['mimeType'],
            ));
          }
        }
        return Future.value(selectImages);
      }
    } catch (err) {
      debugPrint('err：${err.toString()}');
    }
    return Future.value([]);
  }

  @override
  Future<NDFileInfo?> takePicture(
      {bool isWaterMark = false,
      bool isWaterMarkTiled = false,
      List<ImageWaterMarkSettingModel>? waterMarkSettings}) async {
    try {
      var result = await methodChannel.invokeMethod<Map>('takePicture');
      if (result != null) {
        var size = result['size'] as int?;
        var localPath = result['localPath'] as String;
        String name = result['name'] ?? localPath.split('/').last ?? '-';
        if (isWaterMark) {
          localPath = await NDWaterMarkerUtil.watermark<String>(
              [result], waterMarkSettings ?? [], isWaterMarkTiled);
        }
        size = await _fileSize(size, localPath);
        return Future.value(NDFileInfo(
          name: name,
          size: size,
          path: localPath,
          mimeType: result['mimeType'],
        ));
      }
    } catch (err) {
      debugPrint('err：${err.toString()}');
    }
    return Future.value();
  }

  Future<int> _fileSize(int? size, String path) async {
    if (size != null) {
      return size;
    }
    return File(path).length();
  }
}
